using Entity.Player.State;
using MoonFramework.FSM;
using UnityEngine;

namespace Entity.Player
{
    public class PlayerFsm : BaseFsm<Actor>
    {
        public override void Init(string curState, Actor entity)
        {
            base.Init(curState, entity);
            _ = AllocateState(nameof(PlayerIdleState), () => new PlayerIdleState(), InitState);
            _ = AllocateState(nameof(PlayerDeadState), () => new PlayerDeadState(), InitState);
            _ = AllocateState(nameof(PlayerRunState), () => new PlayerRunState(), InitState);
            _ = AllocateState(nameof(PlayerAttackState), () => new PlayerAttackState(), InitState);
            _ = AllocateState(nameof(PlayerWalkState), () => new PlayerWalkState(), InitState);

            AddTransition(nameof(PlayerIdleState), nameof(PlayerRunState));
            AddTransition(nameof(PlayerIdleState), nameof(PlayerAttackState));
            AddTransition(nameof(PlayerIdleState), nameof(PlayerWalkState));
            AddTransition(nameof(PlayerIdleState), nameof(PlayerDeadState));

            AddTransition(nameof(PlayerWalkState), nameof(PlayerIdleState));
            AddTransition(nameof(PlayerWalkState), nameof(PlayerRunState));
            AddTransition(nameof(PlayerWalkState), nameof(PlayerDeadState));

            AddTransition(nameof(PlayerAttackState), nameof(PlayerIdleState));
            AddTransition(nameof(PlayerAttackState), nameof(PlayerDeadState));

            AddTransition(nameof(PlayerRunState), nameof(PlayerWalkState));
            AddTransition(nameof(PlayerRunState), nameof(PlayerIdleState));
            AddTransition(nameof(PlayerRunState), nameof(PlayerDeadState));

            
            fsmStates[curState].Enter();
        }

        private void InitState(BaseState state)
        {
            state.Init(this);
        }

        /// <summary>
        ///     转向目标方向
        /// </summary>
        public void Turn(Vector3 targetDir, float rotationSpeed)
        {
            if (targetDir == Vector3.zero)
                return;

            var targetRotation = Quaternion.LookRotation(targetDir);
            entity.viewController.transform.rotation = Quaternion.Slerp(entity.viewController.transform.rotation,
                targetRotation, Time.deltaTime * rotationSpeed);
        }

        /// <summary>
        ///     移动（使用 CharacterController.Move 来处理碰撞检测）
        /// </summary>
        public void Move(Vector3 targetDir, float speed)
        {
            var move = targetDir * (speed * Time.deltaTime);
            ((PlayerViewController)entity.viewController).moveController.Move(move);
        }
    }
}